package com.itheima.service.impl;

import com.itheima.dao.AccountDao;
import com.itheima.pojo.Account;
import com.itheima.service.AccountService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.jdbc.datasource.DataSourceTransactionManager;
import org.springframework.stereotype.Service;
import org.springframework.transaction.PlatformTransactionManager;
import org.springframework.transaction.TransactionDefinition;
import org.springframework.transaction.TransactionStatus;
import org.springframework.transaction.support.DefaultTransactionDefinition;

import javax.sql.DataSource;

/**
 * @author zhangyan
 * @date 2021/2/3 8:45
 *
 * 1. PlatformTransactionManager  平台事务管理器, 创建事务管理器对象，需要参数数据源
 * 2. TransactionDefinition 事务详情（事务定义、事务属性）
 * 3. TransactionStatus 事务的状态, 接口提供了控制事务执行和查询事务状态的方法
 * 	  提交事务和回滚事务 的事务状态对象必须是同一个
 */
// 了解...
@Service
public class AccountServiceImpl implements AccountService {

    @Autowired
    AccountDao accountDao;
    @Autowired
    DataSource dataSource;
    @Override
    public void transfer(String fromName, String toName, double money) {

        //事务管理器对象
        PlatformTransactionManager transactionManager = null;
        //事务详情对象
        TransactionDefinition transactionDefinition = null;
        //事务状态对象
        TransactionStatus transactionStatus = null;

        try {
            //创建事务管理器对象,必须携带数据源
            transactionManager = new DataSourceTransactionManager(dataSource);
            //创建事务详情对象
            transactionDefinition = new DefaultTransactionDefinition();
            //开启事务,返回事务的状态
            transactionStatus = transactionManager.getTransaction(transactionDefinition);

            //1. 根据用户名查询用户信息
            Account fromAccount = accountDao.findByName(fromName);
            Account toAccount = accountDao.findByName(toName);

            //2. 更改账户余额
            fromAccount.setMoney(fromAccount.getMoney() - money);
            toAccount.setMoney(toAccount.getMoney() + money);

            //3. 更新到数据库
            accountDao.update(fromAccount);
            //如果转账过程出现异常,需要事务回滚
            System.out.println(1/0);
            accountDao.update(toAccount);

            //提交事务
            transactionManager.commit(transactionStatus);

        } catch (Exception e) {
            //如果出现异常，回滚事务
            transactionManager.rollback(transactionStatus);
            e.printStackTrace();

        } finally {
            //关闭资源,spring自动处理
        }
    }
}
